<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
</head>

<body>

</body>
<script>
    // 预编译  
    // arguments  => 函数调用时用于存放实际参数的集合
    // 函数的三种创建方式   声明式 赋值式 自调用 构造函数创建

    // 函数嵌套 (一个函数嵌套调用另一个函数)
    // fn在执行时 有启动了func函数
    // 1. 如果func没有执行完毕, fn并不会结束,等待func()有结果
    // 2. func()的返回值 -> 返回的是func执行的结果 -> 并不会直接作为fn()的结果
    //    如果想fn()  返回func()的执行结果 => 需要在fn函数中return func()的结果

    // function fn() {
    //     var a = 10;  // 局部变量 10  => 11
    //     function func() {
    //         a++;
    //         return a; // 11
    //     }
    //     return func(); // 11
    // }

    // var result = fn();
    // console.log(result);


    // 递归  => 函数在执行过程中嵌套调用了自己

    // 死递归 -> 递归调用自己 -> 根本停不下来 (类似死循环)
    // function fn() {
    //     console.log(111111);
    //     fn();
    // }
    // var result = fn();
    // console.log("result", result);

    // 类比死循环  -
    // var i = 1;
    // while (true) {
    //     console.log(i);
    //     if (i == 100) {   // 跳出条件(临界值)
    //         break;
    //     }
    //     i++;
    // }

    // 改写递归
    // fn() -> fn() -> fn() -> fn() -> fn() -> .... fn(99)  -> fn(100)

    // 先传递 在回归
    // var i = 1;
    // function fn() {
    //     console.log(i);
    //     if (i == 100) {
    //         return i;
    //     }
    //     i++;
    //     return fn();
    // }
    // var result = fn();
    // console.log("result", result);


    // 优化
    // function fn(i) { // 1   起始值
    //     console.log(i); // 1
    //     if (i == 100) {
    //         return i;
    //     }
    //     return fn(i + 1); // fn(2)
    // }
    // var result = fn(1);
    // console.log("result", result);

    // 100 -> 1
    // function fn(i) { // 100   终止值
    //     console.log(i); // 100
    //     if (i == 1) {
    //         return i;
    //     }
    //     return fn(i - 1); // fn(99)
    // }
    // var result = fn(100);
    // console.log("result", result);

    // 求和
    // function fn(i, sum) { // 100  0  |  99 100
    //     console.log(i); // 100   99
    //     sum += i;  // 0+100   | 99 + 100
    //     if (i == 1) {
    //         return sum;
    //     }
    //     return fn(i - 1, sum); // fn(99,100)  fn(98,199)
    // }
    // var result = fn(100, 0);
    // console.log("result", result);

    // 求1-i的和 (i >= 1的正整数)
    // 尾递归
    function fn(i, sum) {  // fn(2,12)
        sum += i;  // 5
        if (i == 1) {
            return sum;
        }
        return fn(i - 1, sum); // fn(1,14) => 15
    }
    var result = fn(5, 0);
    console.log("result", result);

    // 先传递 在回归 
    // fn(5, 0) -> fn(4, 5) -> fn(3, 9) -> fn(2, 12) -> fn(1,14)
    //                                                     ||
    //   15       <-   15    <-   15   <-     15     <-   15









</script>

</html>